Shader "Lch/LitMOES Reflect"
{
    Properties
    {
        [MainTexture] _BaseMap("漫射贴图(_BaseMap)", 2D) = "white" {}
        [MainColor] [HDR]_BaseColor("颜色(_BaseColor)", Color) = (1,1,1,1)
        
        [NoScaleOffset]_BumpScale("法线强度（_BumpScale）", Range(0,4)) = 1.0
        _BumpMap("法线(_BumpMap)", 2D) = "bump" {}

        [NoScaleOffset]_MetallicGlossMap("通道图(_MetallicGlossMap)", 2D) = "white" {}
        _Metallic("金属度（Metallic）", Range(0.0, 1.0)) = 0.0
        _OcclusionStrength("ao强度（_OcclusionStrength）", Range(0.0, 1.0)) = 0.0

   
        [HDR]_EmissionColor("自发光颜色（_EmissionColor）", Color) = (0,0,0,1)
        _Smoothness("粗糙度（Smoothness）", Range(0.0, 1.0)) = 0.7
       // [Toggle]_CustomGGX("自定义高光（无菲涅尔）",float) = 0
       // _SpecPower("高光亮度[_CustomGGX=1]",Range(0,2)) = 1
 
        _BackLight("背光",Range(0,0.5)) = 0.2

         [Toggle(_CUSTOM_SKYBOX)]_CUSTOM_SKYBOX("自定义天空球",Int) = 0
        _CustomCubeTex ("天空球[_CUSTOM_SKYBOX]", Cube) = "_Skybox" {}
        _CustomCubeTexBrightness("天空球亮度[_CUSTOM_SKYBOX] ",Range(0,2)) = 1 

        _ReflectDistance("反射距离",Range(0.3,2.0)) = 1.0
        _ReflectTest("反射测试",Range(0.1,1.0)) = 0.5

        [NoScaleOffset]_SecondNormal("反射扰动法线(_SecondNormal)", 2D) = "bump" {}
        _SecondNormalScale("反射扰动世界缩放（_SecondNormalScale）", Range(0,4)) = 1.0
       _SecondNormalWorldScale("反射扰动混合贴图缩放", Range(0,100)) = 1
       _ScreenRefStrong("屏幕射增强",Range(0,1)) = 0
        _SpecularMaxLimit("光照最大限制",Range(1.0,50)) = 3.0
        /*[Toggle(_UP_LAYER)]_UP_LAYER("混合层",float) = 0
        [NoScaleOffset]_UpperMap("上层混合贴图(_UpperMap)[_UP_LAYER]", 2D) = "white" {}
        _SecondNormalWorldScale("上层混合贴图缩放[_UP_LAYER]", float) = 1
        [NoScaleOffset]_SecondNormal("上层法线(_SecondNormal)[_UP_LAYER]", 2D) = "bump" {}
        [NoScaleOffset]_SecondNormalScale("上层法线强度（_SecondNormalScale）[_UP_LAYER]", Range(0,4)) = 1.0
        [NoScaleOffset]_UpperMetallicGlossMap("上层通道图(_UpperMetallicGlossMap)[_UP_LAYER]", 2D) = "white" {}
        _UpperMetallic("上层金属度（_UpperMetallic）[_UP_LAYER]", Range(0.0, 1.0)) = 0.0
        _UpperOcclusionStrength("上层ao强度（_UpperOcclusionStrength）[_UP_LAYER]", Range(0.0, 1.0)) = 0.0
        [HDR]_UpperEmissionColor("上层自发光颜色（_UpperEmissionColor）[_UP_LAYER]", Color) = (0,0,0,1)
        _UpperSmoothness("上层粗糙度（_UpperSmoothness）[_UP_LAYER]", Range(0.0, 1.0)) = 0.7
        _UpperPower("上层混合程度[_UP_LAYER]",Range(0,1))=0.5
        _UpperEdge("上层过渡[_UP_LAYER]",Range(0.01,0.2)) = 0.1
        _UpperMaxPower("最大混合度[_UP_LAYER]",Range(0.1,1)) = 1
        [Toggle(_EFFECT)]_EFFECT("特效",Int) = 0
         

         
        _DissolveAmount ("消融控制_DissolveAmount[_EFFECT]", Range(0, 1)) = 0.442
        _DissolveEdgeWidth ("消融边的宽度[_EFFECT]", Range(0, 0.5)) = 0.343
        [HDR]_EdgeColor1 ("消融色1[_EFFECT]", Color) = (1, 0.3, 0, 1)
        [HDR]_EdgeColor2 ("消融色2[_EFFECT]", Color) = (0, 0, 0, 1)
        
        [NoScaleOffset]_NoiseTex ("消融图[_EFFECT]", 2D) = "white" {}
        _NoiseScale ("消融图缩放[_EFFECT]", Float) = 1.0
 
         // 新增菲涅尔相关属性
   
        _FresnelPower ("菲涅尔控制[_EFFECT]", Range(0.1, 10)) = 2
        [HDR]_FresnelColor ("菲涅尔颜色[_EFFECT]", Color) = (1.723048, 0.5743492, 0, 1)
        _FresnelIntensity ("菲涅尔程序开关_FresnelColor[_EFFECT]", Range(0, 1)) = 0
        */

        [Toggle(_ALPHATEST_ON)]_ALPHATEST_ON("透明剔除",Int) = 0
		 
         _Cutoff("Alpha Cutoff[_ALPHATEST_ON]", Range(0.0, 1.0)) = 0.5

        [LCHEnum(LCHblendlModel)] _bendModel("混合模式", Int) = 0
 
		[Enum(UnityEngine.Rendering.BlendMode)] _SrcBlend("源混合 SrcBlend", Float) = 1
		[Enum(UnityEngine.Rendering.BlendMode)] _DstBlend("目标混合 DstBlend", Float) = 0
		[Enum(Off, 0, On, 1)]_ZWrite("深度写_ZWrite", float) = 1
		[Enum(UnityEngine.Rendering.CullMode)]_Cull("剔除模式", float) = 2

		_OffsetFactor("双材质防穿插,越小越前", Float) = 0
    }
    SubShader
    {
        Tags
        {
            "RenderPipeline"="UniversalPipeline"
            "RenderType"="Opaque"
            "Queue"="Geometry"
        }

        Pass
        {
            LOD 300
            Name "ForwardLit"
            Tags{"LightMode" = "UniversalForward"}

            Blend[_SrcBlend][_DstBlend]
            ZWrite[_ZWrite]
            Cull[_Cull]
            //Offset -10, 1
            Offset [_OffsetFactor], [_OffsetFactor]
            HLSLPROGRAM
            #define DOUBLE_SIDE
            #define CUSTOM_GGX
            
            //#pragma multi_compile_instancing


            #pragma shader_feature_local_fragment _ALPHATEST_ON

            //#define CUSTOM_CUBEMAP_BRIGHTNESS
            #define _LIGHT_LAYERS
            #define   _SHADOWS_SOFT
            #define _MAIN_LIGHT_SHADOWS_CASCADE
            #define    _ADDITIONAL_LIGHTS
            #pragma multi_compile   _  _CUSTOM_SKYBOX

 
            #pragma multi_compile   _  LIGHTMAP_ON 

            #pragma multi_compile _ SHADOWS_SHADOWMASK
 
            #pragma multi_compile   _ FOG_LINEAR    
 
            //_ADDITIONAL_LIGHT_SHADOWS _LIGHT_LAYERS _MAIN_LIGHT_SHADOWS_CASCADE _SHADOWS_SOFT
            #define _NORMALMAP  

            #define MAIN_LIGHT_CALCULATE_SHADOWS
            #ifdef _NORMALMAP
            #define REQUIRES_WORLD_SPACE_TANGENT_INTERPOLATOR 

            #endif

            #include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Common.hlsl"
            #include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Packing.hlsl"
            #include "Packages/com.unity.render-pipelines.core/ShaderLibrary/Version.hlsl"
            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Input.hlsl"
            #include "Packages/com.unity.render-pipelines.universal/ShaderLibrary/Lighting.hlsl"
          

            #define CUSTOM_VERTEX_PARAM 
            

            #define SCREEN_SPACE_REFLECT 
            #include "lch_global_buffer.hlsl"
            #include "LitMEOSInput.hlsl"
            #include "lch_urp_com.hlsl"
            #include "lch_weather.hlsl"
            #pragma vertex vert
            #pragma fragment frag
          
            
            Varyings vert(Attributes input)
            {
                Varyings output = (Varyings)0;
                UNITY_SETUP_INSTANCE_ID(input);
                UNITY_TRANSFER_INSTANCE_ID(input, output);
                UNITY_INITIALIZE_VERTEX_OUTPUT_STEREO(output);
                FillVaryingsData(input, output);
                output.uv = TRANSFORM_TEX(output.uv, _BaseMap);
                return output;
            }
           
            half3 CalculateBlinnPhong(Light light, InputData inputData)
            {
                half3 attenuatedLightColor = light.color * (light.distanceAttenuation * light.shadowAttenuation);
                half3 lightColor = LightingLambert(attenuatedLightColor, light.direction, inputData.normalWS);
 
                #if defined(_SPECGLOSSMAP) || defined(_SPECULAR_COLOR)
                    half smoothness = exp2(10 * _SpecularColor.a + 1);
                    lightColor += LightingSpecular(attenuatedLightColor, light.direction, inputData.normalWS, inputData.viewDirectionWS, half4(_SpecularColor.rgb, 1), smoothness);
                #endif

                return lightColor;
            }
             #ifdef _SSS
            half3 LightingSSS(half3 lightColor ,half3 lightDirectionWS,half3 normalWS,half3 sssColor )
            {
 
                half NdotL =  dot(normalWS, lightDirectionWS) ;
    
                float3 sss  = 0.2*exp(-3.*abs(NdotL)/(sssColor+0.001));
   
                return sssColor *   sss;

            }
            half3 LightingSSS(Light light,half3 normalWS,LchSurfaceData surfaceData)
            {
 
                return LightingSSS(light.color.rgb,light.direction,normalWS ,surfaceData.sssColor.rgb );
 
            }
            #endif
            half4 frag(Varyings input,bool isFrontFace : SV_IsFrontFace) : SV_Target
            {
                UNITY_SETUP_INSTANCE_ID(input);
                UNITY_SETUP_STEREO_EYE_INDEX_POST_VERTEX(input);
                 
                float2 uv = input.uv;

               
                

                LchSurfaceData surfaceData;
                InitializeLchSurfaceData(input.uv,input.color, surfaceData);
                

                #ifdef SCREEN_SPACE_REFLECT
                rayStartWS = input.positionWS;
                 
                
                #endif
                 
          
 
                
                InputData inputData;
                InitializeInputData(input,  isFrontFace,  surfaceData.normalTS, inputData);
                

                #ifdef SCREEN_SPACE_REFLECT
                InitializeRefNoise(surfaceData ,uv,input.positionWS,input.normalWS, input.tangentWS,inputData.viewDirectionWS);
                //return float4(inputData.normalWS*0.5+0.5,1);
                //return float4(noistReflectVector*0.5+0.5,1);
                #endif

                Weather(surfaceData, inputData, input.normalWS,input.positionWS);

               
                BRDFData brdfData;
                InitializeBRDFData(surfaceData , brdfData);

                
                
                //inputData.normalWS

                LchAnisoData anisoData;
                InitAnisoData(surfaceData,anisoData,inputData);
                half4 shadowMask = CalculateShadowMask(inputData);
                shadowMask = 0.2+shadowMask*0.8;
                AmbientOcclusionFactor aoFactor;
                aoFactor.directAmbientOcclusion = 1.0;
                aoFactor.indirectAmbientOcclusion = surfaceData.occlusion;
 
                Light mainLight = GetMainLight(inputData, shadowMask, aoFactor);
                half3 ambient = inputData.bakedGI.rgb;
             
                MixRealtimeAndBakedGI(mainLight, inputData.normalWS, inputData.bakedGI);

                

                float NDotV;
                half3 giColor = LchGlobalIllumination(brdfData, inputData.bakedGI, aoFactor.indirectAmbientOcclusion, inputData.normalWS, inputData.viewDirectionWS,NDotV);
 
                #ifdef _SSS
                giColor *= surfaceData.sssAmb;
                #endif
                uint meshRenderingLayers = GetMeshRenderingLayer();
                half3 color = giColor; 
      
               
               
 
                if (IsMatchingLightLayer(mainLight.layerMask, meshRenderingLayers))
                {

                    
                    if(mainLight.direction.y>0.9999 && LchMainLightParams.w>0.5)
                    {   
                        mainLight.direction = normalize (LchMainLightParams.xyz-inputData.positionWS);
                    }
       
                    if(surfaceData.backLight>0)
                    {
                        color += LchLightingPhysicallyBasedBackLight(brdfData,anisoData, mainLight.color, mainLight.direction,   mainLight.shadowAttenuation, inputData.normalWS, inputData.viewDirectionWS,surfaceData.backLight ) ;  
                    }
                    else
                    {
                        color += LchLightingPhysicallyBased(brdfData,anisoData, mainLight.color, mainLight.direction,   mainLight.shadowAttenuation, inputData.normalWS, inputData.viewDirectionWS );  
                    }
                  
                    #ifdef _SSS
                    color.rgb += LightingSSS(mainLight,inputData.normalWS,surfaceData);
                    #endif
                      
                }
 
               #if defined(_ADDITIONAL_LIGHTS)
           
              uint pixelLightCount = GetAdditionalLightsCount();

 
              
                #if USE_CLUSTERED_LIGHTING
                for (uint lightIndex = 0; lightIndex < min(_AdditionalLightsDirectionalCount, MAX_VISIBLE_LIGHTS); lightIndex++)
                {
                    Light light = GetAdditionalLight(lightIndex, inputData, shadowMask, aoFactor);
                    if (IsMatchingLightLayer(light.layerMask, meshRenderingLayers))
                    {
                    
                        color += LchLightingPhysicallyBased(brdfData,anisoData, light.color, light.direction, light.distanceAttenuation * light.shadowAttenuation, inputData.normalWS, inputData.viewDirectionWS);  
                        
                    }
                    
                }
                #endif
               
                LIGHT_LOOP_BEGIN(pixelLightCount)
                    Light light = GetAdditionalLight(lightIndex, inputData, shadowMask, aoFactor);
                    if (IsMatchingLightLayer(light.layerMask, meshRenderingLayers))
                    {
                        color += LchLightingPhysicallyBased(brdfData,anisoData, light.color, light.direction, light.distanceAttenuation * light.shadowAttenuation, inputData.normalWS, inputData.viewDirectionWS);    
                    
                    }
                LIGHT_LOOP_END
                #endif
                #if defined(_ADDITIONAL_LIGHTS_VERTEX)
                lightingData.vertexLightingColor += inputData.vertexLighting * surfaceData.albedo;
                #endif

                color.rgb = min(color.rgb,surfaceData.maxLimit);

                
                color.rgb += surfaceData.emission;

                #if _EFFECT

                if(_DissolveAmount>0)
                {
                    half noise = SAMPLE_TEXTURE2D(_NoiseTex, sampler_NoiseTex, input.uv*_NoiseScale).r;
                    // 计算消融因子 (噪声值减去消融量)
                    half dissolveFactor = noise - _DissolveAmount + _DissolveEdgeWidth;
                    // 完全消融的部分直接丢弃
                    clip(dissolveFactor);
                    //half3 edgeColor =  _EdgeColor1.rgb;
                    // 计算边缘区域 (两层颜色过渡区域)
                    half edgeFactor = smoothstep(0, _DissolveEdgeWidth , dissolveFactor);
                    half3 edgeColor = lerp(_EdgeColor2.rgb, _EdgeColor1.rgb, edgeFactor*edgeFactor); 
                    // 混合边缘颜色和基础颜色
                    color.rgb *= lerp(edgeColor.rgb, 1.0, edgeFactor);
                }
                

                float invNdotV = 1.0- NDotV;

                color.rgb = lerp(color.rgb,_FresnelColor.rgb,pow(invNdotV,_FresnelPower)*_FresnelIntensity);
                


              
                #endif
                color.rgb = MixFog(color.rgb, inputData.fogCoord);
               return float4(color,surfaceData.alpha);
            }
            ENDHLSL
        }

        
         
    }
    FallBack "Lch/LitMOES"

    CustomEditor "LCHShaderGUIBase" 
}